package com.lamer.console.base.service.impl;

import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.lamer.console.base.dto.UpdatePasswordParam;
import com.lamer.console.base.dto.UserDto;
import com.lamer.console.base.entity.User;
import com.lamer.console.base.mapper.UserMapper;
import com.lamer.console.base.service.IBaseService;
import com.lamer.console.base.service.IUserService;
import com.lamer.console.common.exception.Asserts;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.data.redis.core.ValueOperations;
import org.springframework.security.crypto.password.PasswordEncoder;
import org.springframework.stereotype.Service;

import javax.annotation.Resource;

/**
 * <p>
 *  服务实现类
 * </p>
 *
 * @author 黄诗鹏
 * @since 2021-09-25
 */
@Service("UserServiceImpl")
public class UserServiceImpl extends ServiceImpl<UserMapper, User>  implements IUserService, IBaseService {

    @Resource
    private UserMapper userMapper;

    @Autowired
    private PasswordEncoder passwordEncoder;

    @Autowired
    private RedisTemplate<String, String> redisTemplate;

    @Override
    public User getUserByUserId(int id) {
        QueryWrapper<User> queryWrapper = new QueryWrapper<>();
        queryWrapper.lambda().eq(User::getId, id);
        return userMapper.selectOne(queryWrapper);
    }

    @Override
    public User getUserByUsername(String username) {
        QueryWrapper<User> queryWrapper = new QueryWrapper<>();
        queryWrapper.lambda().eq(User::getUsername, username);
        return userMapper.selectOne(queryWrapper);
    }

    @Override
    public UserDto getUserDtoByUserName(String username) {
        User user = getUserByUsername(username);
        UserDto userDto = new UserDto();
        BeanUtils.copyProperties(user, userDto);
        return userDto;
    }

    @Override
    public boolean postUser(User user) {
        QueryWrapper<User> userQueryWrapper = new QueryWrapper<>();
        userQueryWrapper.lambda().eq(User::getUsername, user.getUsername());
        User one = userMapper.selectOne(userQueryWrapper);
        if(one != null){
            Asserts.fail("该用户已经存在");
        }
        user.setPassword(passwordEncoder.encode("123456"));
        int insert = userMapper.insert(user);
        return insert > 0;
    }


    @Override
    public boolean putUser(User user) {
        QueryWrapper<User> queryWrapper = new QueryWrapper<>();
        queryWrapper.lambda().eq(User::getId, user.getId());
        User oldUser = userMapper.selectOne(queryWrapper);
        if(oldUser == null){
            Asserts.fail("用户不存在");
        }
        user.setPassword(passwordEncoder.encode(oldUser.getPassword()));
        int update = userMapper.updateById(user);
        return update >= 1;
    }

    @Override
    public boolean updatePassword(int id, UpdatePasswordParam updatePasswordParam) {
        User user = getUserByUserId(id);
        if(!passwordEncoder.matches(updatePasswordParam.getOldPassword(), user.getPassword())){
            Asserts.fail("原密码错误");
        }else if(!updatePasswordParam.getPassword().equals(updatePasswordParam.getConfirmPassword())){
            Asserts.fail("两次输入的密码不一致");
        }
        user.setPassword(passwordEncoder.encode(updatePasswordParam.getPassword()));
        int update = userMapper.updateById(user);
        return update >= 1;
    }

    @Override
    public boolean resetPassword(int id) {
        ValueOperations<String, String> operations = redisTemplate.opsForValue();
        String resetPassword = operations.get("PASSWORD.RESET");

        User user = userMapper.selectById(id);
        user.setPassword(passwordEncoder.encode(resetPassword));

        int update = userMapper.updateById(user);
        return update >= 1;
    }

    @Override
    public boolean updateStatusById(int id) {
        User user = getUserByUserId(id);
        int status = user.getStatus() == 1 ? 0 : 1;
        user.setStatus(status);
        int update = userMapper.updateById(user);
        return update >= 1;
    }

}
